package com.fiona.ioc.load;


import java.lang.reflect.Method;
import java.util.List;
import java.util.Map;

import com.fiona.common.base.InitBean;
import com.fiona.common.constant.FionaConstant;
import com.fiona.common.constant.FionaSpace;
import com.fiona.core.load.LoadHelper;
import com.fiona.core.load.WriteFields;
import com.fiona.core.model.FionaBeanClassModel;
import com.fiona.core.model.FionaBeanModel;
import com.fiona.ioc.factory.BeanFactory;

/**
 * 加载FionaBean
 * @author huacongnan
 *
 */
public class LoadFionaBean {
	
	/**
	 * 获取全局存储空间 
	 */
	private static FionaSpace constants = FionaSpace.getFionaSpace();

	/**
	 * 创建FionaBean对象，并完成对象注入
	 *
	 * @throws Exception 异常
	 */
	public static void loadBean() throws Exception{
		try {
			/* 获取所有的bean数据 */
			List<FionaBeanClassModel> fionaBeansList = LoadHelper.getBeanList();
			
			/* 创建bean对象，并保存起来 */
			Map<String, FionaBeanModel> fionaBeanObjects = LoadHelper.getBeanObjectMap();
			for(FionaBeanClassModel fionaBeanClassModel : fionaBeansList) {

				Class<?> cls = fionaBeanClassModel.getClassName();
				String beanName = LoadHelper.getBeanName(fionaBeanClassModel,cls);

				if(fionaBeanObjects.get(beanName) == null) {
					FionaBeanModel beanModel = new FionaBeanModel();
					beanModel.setName(beanName);
					beanModel.setCls(cls);
					beanModel.setObj(BeanFactory.createBean(cls));
					fionaBeanObjects.put(beanName, beanModel);
				} else {
					throw new Exception("已经存在name为["+beanName+"]的bean了");
				}
			}

			/* 注入对象 */
			iocBean(fionaBeanObjects);
			/* 初始化FionaBean */
			initBean(fionaBeanObjects);
		} catch (Exception e) {
			throw new Exception("加载并注入FionaBean的时候出现错误",e);
		} 
	}
	
	/**
	 * FionaBean注入
	 * @param fionaBeanObjects 对象
	 * @throws Exception 异常
	 */
	private static void iocBean(Map<String, FionaBeanModel> fionaBeanObjects) throws Exception{
		try {
			for(String key : fionaBeanObjects.keySet()) {
				FionaBeanModel fionaBeanModel = fionaBeanObjects.get(key);
				Object obj = fionaBeanModel.getObj();
				Class<?> cls = fionaBeanModel.getCls();

				/* 获取对象属性，完成注入 */
				WriteFields.writeFields(cls,obj,fionaBeanObjects);

				/* 保险起见，重新插入数据 */
				fionaBeanModel.setCls(cls);
				fionaBeanObjects.put(key, fionaBeanModel);
			}
			
			constants.setAttr(FionaConstant.FIONA_BEAN_OBJECTS, fionaBeanObjects);
		} catch (Exception e) {
			throw new Exception("加载并注入FionaBean的时候出现错误",e);
		} 
	}

	/**
	 * 执行InitBean接口FionaBean类init初始化方法
	 * @param fionaBeanObjects 对象
	 * @throws Exception 异常
	 */
	private static void initBean(Map<String, FionaBeanModel> fionaBeanObjects) throws Exception {
		try {
			for(String key : fionaBeanObjects.keySet()){
				FionaBeanModel fionaBeanModel = fionaBeanObjects.get(key);
				Object obj = fionaBeanModel.getObj();
				if(obj instanceof InitBean){
					Class<?> cls = fionaBeanModel.getCls();

					Method method = cls.getMethod("init");
					method.invoke(obj);
				}
			}
		} catch (Exception e){
			throw new Exception("初始化FionaBean的时候出现错误",e);
		}
	}
}
